
const _interopRequireDefault = require('@babel/runtime/helpers/interopRequireDefault');

exports.__esModule = true;
exports.default = void 0;

const _utils = require('../utils');

const _event = require('../utils/dom/event');

const _touch = require('../mixins/touch');

const _field = require('../mixins/field');

const _icon = _interopRequireDefault(require('../icon'));

// Utils
// Mixins
// Components
const _createNamespace = (0, _utils.createNamespace)('rate');
const createComponent = _createNamespace[0];
const bem = _createNamespace[1];

function getRateStatus(value, index, allowHalf) {
  if (value >= index) {
    return 'full';
  }

  if (value + 0.5 >= index && allowHalf) {
    return 'half';
  }

  return 'void';
}

const _default = createComponent({
  mixins: [_touch.TouchMixin, _field.FieldMixin],
  props: {
    size: [Number, String],
    color: String,
    gutter: [Number, String],
    readonly: Boolean,
    disabled: Boolean,
    allowHalf: Boolean,
    voidColor: String,
    iconPrefix: String,
    disabledColor: String,
    value: {
      type: Number,
      default: 0,
    },
    icon: {
      type: String,
      default: 'star',
    },
    voidIcon: {
      type: String,
      default: 'star-o',
    },
    count: {
      type: [Number, String],
      default: 5,
    },
    touchable: {
      type: Boolean,
      default: true,
    },
  },
  computed: {
    list: function list() {
      const list = [];

      for (let i = 1; i <= this.count; i++) {
        list.push(getRateStatus(this.value, i, this.allowHalf));
      }

      return list;
    },
    sizeWithUnit: function sizeWithUnit() {
      return (0, _utils.addUnit)(this.size);
    },
    gutterWithUnit: function gutterWithUnit() {
      return (0, _utils.addUnit)(this.gutter);
    },
  },
  mounted: function mounted() {
    this.bindTouchEvent(this.$el);
  },
  methods: {
    select: function select(index) {
      if (!this.disabled && !this.readonly && index !== this.value) {
        this.$emit('input', index);
        this.$emit('change', index);
      }
    },
    onTouchStart: function onTouchStart(event) {
      const _this = this;

      if (this.readonly || this.disabled || !this.touchable) {
        return;
      }

      this.touchStart(event);
      const rects = this.$refs.items.map((item) => item.getBoundingClientRect());
      const ranges = [];
      rects.forEach((rect, index) => {
        if (_this.allowHalf) {
          ranges.push({
            score: index + 0.5,
            left: rect.left,
          }, {
            score: index + 1,
            left: rect.left + rect.width / 2,
          });
        } else {
          ranges.push({
            score: index + 1,
            left: rect.left,
          });
        }
      });
      this.ranges = ranges;
    },
    onTouchMove: function onTouchMove(event) {
      if (this.readonly || this.disabled || !this.touchable) {
        return;
      }

      this.touchMove(event);

      if (this.direction === 'horizontal') {
        (0, _event.preventDefault)(event);
        const { clientX } = event.touches[0];
        this.select(this.getScoreByPosition(clientX));
      }
    },
    getScoreByPosition: function getScoreByPosition(x) {
      for (let i = this.ranges.length - 1; i > 0; i--) {
        if (x > this.ranges[i].left) {
          return this.ranges[i].score;
        }
      }

      return this.allowHalf ? 0.5 : 1;
    },
    genStar: function genStar(status, index) {
      const _this2 = this;

      const h = this.$createElement;
      const { icon } = this;
      const { color } = this;
      const { count } = this;
      const { voidIcon } = this;
      const { disabled } = this;
      const { voidColor } = this;
      const { disabledColor } = this;
      const score = index + 1;
      const isFull = status === 'full';
      const isVoid = status === 'void';
      let style;

      if (this.gutterWithUnit && score !== +count) {
        style = {
          paddingRight: this.gutterWithUnit,
        };
      }

      return h('div', {
        ref: 'items',
        refInFor: true,
        key: index,
        attrs: {
          role: 'radio',
          tabindex: '0',
          'aria-setsize': count,
          'aria-posinset': score,
          'aria-checked': String(!isVoid),
        },
        style,
        class: bem('item'),
      }, [h(_icon.default, {
        attrs: {
          size: this.sizeWithUnit,
          name: isFull ? icon : voidIcon,
          color: disabled ? disabledColor : isFull ? color : voidColor,
          classPrefix: this.iconPrefix,
          'data-score': score,
        },
        class: bem('icon', {
          disabled,
          full: isFull,
        }),
        on: {
          click: function click() {
            _this2.select(score);
          },
        },
      }), this.allowHalf && h(_icon.default, {
        attrs: {
          size: this.sizeWithUnit,
          name: isVoid ? voidIcon : icon,
          color: disabled ? disabledColor : isVoid ? voidColor : color,
          classPrefix: this.iconPrefix,
          'data-score': score - 0.5,
        },
        class: bem('icon', ['half', {
          disabled,
          full: !isVoid,
        }]),
        on: {
          click: function click() {
            _this2.select(score - 0.5);
          },
        },
      })]);
    },
  },
  render: function render() {
    const _this3 = this;

    const h = arguments[0];
    return h('div', {
      class: bem({
        readonly: this.readonly,
        disabled: this.disabled,
      }),
      attrs: {
        tabindex: '0',
        role: 'radiogroup',
      },
    }, [this.list.map((status, index) => _this3.genStar(status, index))]);
  },
});

exports.default = _default;
